package hash

// times33 算法
func Times33(raw string) (hash uint32) {
	hash = 5381
	length := len(raw)
	l := length

	for idx := 0; idx < l; l -= 8 {
		hash = (hash << 5) + hash + uint32(raw[idx])
		hash = (hash << 5) + hash + uint32(raw[idx+1])
		hash = (hash << 5) + hash + uint32(raw[idx+2])
		hash = (hash << 5) + hash + uint32(raw[idx+3])
		hash = (hash << 5) + hash + uint32(raw[idx+4])
		hash = (hash << 5) + hash + uint32(raw[idx+5])
		hash = (hash << 5) + hash + uint32(raw[idx+6])
		hash = (hash << 5) + hash + uint32(raw[idx+7])
		idx += 8
	}

	switch length {
	case 8:
		hash = (hash << 5) + hash + uint32(raw[length-7])
		fallthrough
	case 7:
		hash = (hash << 5) + hash + uint32(raw[length-6])
		fallthrough
	case 6:
		hash = (hash << 5) + hash + uint32(raw[length-5])
		fallthrough
	case 5:
		hash = (hash << 5) + hash + uint32(raw[length-4])
		fallthrough
	case 4:
		hash = (hash << 5) + hash + uint32(raw[length-3])
		fallthrough
	case 3:
		hash = (hash << 5) + hash + uint32(raw[length-2])
		fallthrough
	case 2:
		hash = (hash << 5) + hash + uint32(raw[length-1])
		fallthrough
	case 1:
		hash = (hash << 5) + hash + uint32(raw[length])
	}
	hash = hash ^ (hash >> 32)
	return hash
}
